package com.mg.sms;

import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.Properties;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import javax.mail.Address;
import javax.mail.BodyPart;
import javax.mail.Folder;
import javax.mail.Message;
import javax.mail.MessagingException;
import javax.mail.Multipart;
import javax.mail.Session;
import javax.mail.Store;
import javax.mail.internet.MimeUtility;
import javax.mail.search.OrTerm;
import javax.mail.search.SubjectTerm;

import android.app.Activity;
import android.content.ContentValues;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.util.Log;

import com.mg.sms.bean.SMSBean;
import com.mg.sms.dao.DBHelper;
import com.mg.sms.dao.SMSConstant;

public class GmailManager {
    
    private static final String IMAPS_PROTOCOL= "imaps";
    
    private static final String IMAPS_MAIL_HOTS = "imap.gmail.com";
    
    private static final String MAIL_BOX = "Inbox";
    
    private static Pattern telPattern = Pattern.compile("\\d{10}");
    
    
    /**
     * 將gmail信件轉入DB存放
     * @param activity
     * @param username
     * @param Password
     */
    public static void mailSyncToDB(Activity activity, String username, String Password) {
        DBHelper dbHelper = null;
        SQLiteDatabase sqliteDatabase = null;
        try {
            dbHelper = new DBHelper(activity);
            sqliteDatabase = dbHelper.getWritableDatabase();
            List<Message> messageList = receiveMail(username, Password);
            for(Message message : messageList) {
                SMSBean sms = new SMSBean();
                sms.setSubject(MimeUtility.decodeText(message.getSubject()));
                sms.setForm(getFromAddress(message.getFrom()));
                sms.setReceivedDate(String.valueOf(message.getReceivedDate().getTime()));
                sms.setTel(getTel(MimeUtility.decodeText(message.getSubject())));
                sms.setBody(getMailContent((Multipart)message.getContent()));
               
                Cursor cursor =sqliteDatabase.rawQuery("SELECT * FROM SMS WHERE SMS_FROM = ? AND SMS_RECEIVED_DATE = ?" , new String[]{sms.getForm(), sms.getReceivedDate()});
                if(cursor.getCount() == 0) {
                    ContentValues values = new ContentValues();
                    values.put(SMSConstant.SMS_SUBJECT,       sms.getSubject());
                    values.put(SMSConstant.SMS_FROM,          sms.getForm());
                    values.put(SMSConstant.SMS_RECEIVED_DATE, sms.getReceivedDate());
                    values.put(SMSConstant.SMS_TEL,           sms.getTel());
                    values.put(SMSConstant.SMS_STATUS,        SMSConstant.STATUS_INCOMPLETE);
                    values.put(SMSConstant.SMS_BODY,          sms.getBody());
                    sqliteDatabase.insert(SMSConstant.TABLE_NAME, null, values);
                }
            }
        } catch(Exception ex) {
            ex.printStackTrace();
            Log.d("bear", ex.getMessage(), ex);
        } finally {
            if(sqliteDatabase!= null) sqliteDatabase.close();
        }
    }
        
    /**
     * 收取Gmail信件
     * @param username
     * @param Password
     * @return
     */
    private static List<Message> receiveMail(String username, String Password) {
        List<Message> messageList =  new ArrayList<Message>();
        
        try {
            // 設置電子郵件協議
            Properties props = System.getProperties();
            props.setProperty("mail.store.protocol", IMAPS_PROTOCOL);
            
            // 進行連線
            Session session = Session.getDefaultInstance(props, null );
            session.setDebug(true);
            Store store = session.getStore(IMAPS_PROTOCOL);
            store.connect(IMAPS_MAIL_HOTS , username, Password);
            
            // 取得信件內容
            Folder inbox = store.getFolder(MAIL_BOX);
            inbox.open(Folder.READ_ONLY);
            Message messages[] = inbox.search(new OrTerm(new SubjectTerm("sms["), new SubjectTerm("sms[")));
            for (Message message : messages) {
                messageList.add(message);
            }
        } catch(Exception ex) {
            ex.printStackTrace();
            Log.e("receiveMail", ex.getMessage(), ex);
        }
        return messageList;
    }
    
    /**
     * 取得信件內容
     * @param multipart
     * @return
     * @throws IOException
     * @throws MessagingException
     */
    private static String getMailContent(Multipart multipart) throws IOException, MessagingException{
        StringBuffer content = new StringBuffer();
        for (int x = 0; x < multipart.getCount(); x++) {
            BodyPart bodyPart = multipart.getBodyPart(x);
            String disposition = bodyPart.getDisposition();
            if (disposition != null && (disposition.equals(BodyPart.ATTACHMENT))) {
            } else {
                content.append(multipart.getBodyPart(x).getContent());
            }
        }
        return content.toString();
    }
    
    /**
     * 取得手機號碼
     * @param inputStr
     * @return
     */
    private static String getTel(String inputStr) {
        StringBuffer sb = new StringBuffer();
        Matcher matcher = telPattern.matcher(inputStr);
        boolean matchFound = matcher.find();
        while(matchFound) {
            for (int i = 0; i <= matcher.groupCount(); i++) {
                sb.append(matcher.group(i)).append(",");
            }
            if (matcher.end() + 1 <= inputStr.length()) {
                matchFound = matcher.find(matcher.end());
            } else {
                break;
            }
        }
        return sb.toString();
    }

    /**
     * 取得寄件者
     * @param addressList
     * @return
     */
    private static String getFromAddress(Address[] addressList) {
        StringBuffer sb = new StringBuffer();
        for(Address address : addressList) sb.append(address.toString());
        return sb.toString();
    }
     
}
